#include "stm32f10x.h"
#include <stdio.h>
#include "lcd.h"
#include "key.h"
#include "adc.h"

#define UPPER  0
#define LOWER  1
#define NORMAL 2

#define LED_ENABLE(pin)  	GPIO_SetBits(GPIOD, GPIO_Pin_2); \
							GPIO_Write(GPIOC, pin); \
							GPIO_ResetBits(GPIOD, GPIO_Pin_2)					
u32 TimingDelay = 0;
uint8_t led_flag = 0;
uint8_t led_count = 0;
struct data{ //定义一个结构，方便使用
	float Volt;
	float Max_Volt;
	float Min_Volt;
	int LED_upper;
	int LED_lower;
};

void Delay_Ms(u32 nTime);
void display_main(float val, uint8_t status);
void My_LCD_DisplayStringLine(u8 Line, u8 *ptr, uint8_t high);
void display_set(uint8_t line, struct data input_data);
void led_gpio_config(void);
uint16_t clrbit(uint16_t x,uint16_t y);
//Main Body
int main(void)
{
	uint8_t option = 1; //指定高亮的那个选项
	struct data volt_data = {0, 2.4, 1.8, 1,2}; //初始化结构体
	uint8_t key_val; //接收按键值
	uint8_t main_window = 1; //主窗口和设置窗口切换
	/****系统初始化*****/
	SysTick_Config(SystemCoreClock/1000);
	STM3210B_LCD_Init();
	led_gpio_config();
	key_gpio_config();
	PB0_ADC_Init();
	LCD_Clear(Black);
	LCD_SetBackColor(Black);
	LCD_SetTextColor(White);
	
	while(1)
	{
		LCD_Clear(Black);
		while(main_window == 1)
		{
			key_val = key_drive();
			volt_data.Volt = get_adcVal();
			if(volt_data.Volt< volt_data.Min_Volt)
			{
				display_main(volt_data.Volt, LOWER);	
				led_flag = 1;
				if(led_count == 1)
				{
					LED_ENABLE(clrbit(0xff00, volt_data.LED_lower + 7));
				}
				else if(led_count == 0)
				{
					LED_ENABLE(0xff00);
				}
			}
			else if(volt_data.Volt >  volt_data.Max_Volt)
			{
				display_main(volt_data.Volt, UPPER);
				led_flag = 1;
				if(led_count == 1)
				{
					LED_ENABLE(clrbit(0xff00, volt_data.LED_upper + 7));
				}
				else if(led_count == 0)
				{
					LED_ENABLE(0xff00);
				}
			}
			else
			{
				display_main(volt_data.Volt, NORMAL);
				led_flag = 0;
				LED_ENABLE(0xff00);
			}
			if(key_val == 0x11)
			{
				main_window = 0;
			}
		}
		LCD_Clear(Black);
		led_flag = 0;
		LED_ENABLE(0xff00);
		while(main_window == 0)
		{
		
			key_val = key_drive();
			if(0x12 == key_val)
			{
				option = option +1;
				if(option >= 5)
				{
					option = 1;
				}
			}
			if(0x13 == key_val)
			{
				switch(option)
				{
					case 1: volt_data.Max_Volt = volt_data.Max_Volt + 0.3; 
						if(volt_data.Max_Volt > 3.3)
						{
							volt_data.Max_Volt = 0;
						}
						break;
					case 3: volt_data.LED_upper = volt_data.LED_upper + 1;
						if(volt_data.LED_upper > 8)
						{
							volt_data.LED_upper = 1;
						}
						break;
					default: break;	
				}
			}
			if(0x14 == key_val)
			{
				switch(option)
				{
					case 2: volt_data.Min_Volt = volt_data.Min_Volt - 0.3; 
						if(volt_data.Min_Volt < 0)
						{
							volt_data.Min_Volt = 3.3;
						}
						break;
					case 4: volt_data.LED_lower = volt_data.LED_lower - 1;
						if(volt_data.LED_lower <= 0)
						{
							volt_data.LED_lower = 8;
						}
						break;
					default: break;	
				}
			}
			display_set(option, volt_data);
			if(key_val == 0x11)
			{
				if((volt_data.LED_lower != volt_data.LED_upper) && (volt_data.Min_Volt < volt_data.Max_Volt))
				{
					main_window = 1;
					option = 1;
				}
				else
				{
					main_window = 0;
					option = 1;	

					LCD_SetBackColor(Red);
					LCD_SetTextColor(White);
					if(volt_data.LED_lower == volt_data.LED_upper)
					{
						LCD_DisplayStringLine(Line8, (uint8_t *)"ERROR LED  !!");
					}
					else if(volt_data.Min_Volt > volt_data.Max_Volt)
					{
						LCD_DisplayStringLine(Line8, (uint8_t *)"ERROR Volt !!");
					}
					else
					{
						LCD_DisplayStringLine(Line8, (uint8_t *)"ERROR All  !!");
					}
					LCD_SetBackColor(Black);
					LCD_SetTextColor(White);					
				}
			}
		}
		
		
	}
}
//这个函数是讲指定的为置零，方便操作LED灯
uint16_t clrbit(uint16_t x,uint16_t y)
{
	return x&=~(1<<y);
}

//主显示函数
void display_main(float val, uint8_t status)
{
	char str_text[20];
	LCD_DisplayStringLine(Line3, (uint8_t *)"        Main   ");
	sprintf(str_text, "    Volt:%.1fV ",val);
	LCD_DisplayStringLine(Line5, (uint8_t *)str_text);
	switch(status)
	{
		case UPPER:  LCD_DisplayStringLine(Line6, (uint8_t *)"    Status:Upper "); break;
		case LOWER:  LCD_DisplayStringLine(Line6, (uint8_t *)"    Status:Lower "); break;
		case NORMAL: LCD_DisplayStringLine(Line6, (uint8_t *)"    Status:Normal"); break;
	}
}

//设置界面
void display_set(uint8_t line, struct data input_data)
{
	char str_text[30];
	uint8_t i = 0; 
	uint8_t flag[4] = {0};
	if(line == 3) line = 4;
	else if(line == 4) line = 8;
	else if(line > 4) line = 1;
	for(i = 0; i < 4; i ++)
	{
		flag[i] = line % 2;
		line = line /2;
	}
	My_LCD_DisplayStringLine(Line3, (uint8_t *)"        Setting   ",0);
	sprintf(str_text, "    Max Volt:%.1fV    ",input_data.Max_Volt);
	My_LCD_DisplayStringLine(Line4, (uint8_t *)str_text,flag[0]);
	sprintf(str_text, "    Min Volt:%.1fV    ",input_data.Min_Volt);
	My_LCD_DisplayStringLine(Line5, (uint8_t *)str_text,flag[1]);
	sprintf(str_text, "    Upper:LD%d        ",input_data.LED_upper);
	My_LCD_DisplayStringLine(Line6, (uint8_t *)str_text,flag[2]);
	sprintf(str_text, "    Lower:LD%d        ",input_data.LED_lower);
	My_LCD_DisplayStringLine(Line7, (uint8_t *)str_text,flag[3]);

}

void My_LCD_DisplayStringLine(u8 Line, u8 *ptr, uint8_t high)
{
	u32 i = 0;
	u16 refcolumn = 319;//319;
	if(high)
	{
		LCD_SetBackColor(White);
		LCD_SetTextColor(Black);	
	}
	else
	{
		LCD_SetBackColor(Black);
		LCD_SetTextColor(White);
	}
	while ((*ptr != 0) && (i < 20))	 //	20
	{
		LCD_DisplayChar(Line, refcolumn, *ptr);
		refcolumn -= 16;
		ptr++;
		i++;
	}	
	LCD_SetBackColor(Black);
	LCD_SetTextColor(White);
}

void led_gpio_config(void)
{
	GPIO_InitTypeDef gpio_structure;
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOD, ENABLE);
	
	gpio_structure.GPIO_Mode = GPIO_Mode_Out_PP;
	gpio_structure.GPIO_Speed = GPIO_Speed_50MHz;
	gpio_structure.GPIO_Pin = GPIO_Pin_2;
	GPIO_Init(GPIOD, &gpio_structure);
	
	GPIO_SetBits(GPIOD, GPIO_Pin_2);
	GPIO_Write(GPIOC, 0xffFF);
	GPIO_ResetBits(GPIOD, GPIO_Pin_2);
}
//
void Delay_Ms(u32 nTime)
{
	TimingDelay = nTime;
	while(TimingDelay != 0);	
}
